Shader "Custom/ToonBody"
{
    Properties
    {
        [MainTexture] _BaseMap("Base Map (RGB Diffuse)", 2D) = "white" {}
        [MainColor] _BaseColor("Base Color", Color) = (1,1,1,1)
        
        // --- 皮肤 NPR ---
        _BrightColor("亮部颜色", Color) = (1,1,1,1)
        _MidColor("过渡颜色", Color) = (1,0.6,0.6,1) 
        _DarkColor("暗部颜色", Color) = (0.7,0.4,0.4,1)
        _BrightThreshold("亮部阈值", Range(0, 1)) = 0.6
        _DarkThreshold("暗部阈值", Range(0, 1)) = 0.3
        _ShadowSmooth("明暗过渡平滑度", Range(0, 0.2)) = 0.05
        [Toggle(_SPECULAR)] _ToonSpecular("皮肤高光", Float) = 1 // 重命名以区分PBR高光
        _ToonSpecularColor("皮肤高光颜色", Color) = (1,1,1,1)
        _ToonSpecularSize("皮肤高光大小", Range(0, 1)) = 0.2
        _ToonSpecularSmoothness("皮肤高光平滑度", Range(0, 0.2)) = 0.05
        // [Toggle(_RIM_LIGHTING)] _RimLighting("边缘光", Float) = 1
        // _RimColor("边缘光颜色", Color) = (1,0.8,0.8,1)
        // _RimPower("边缘光强度", Range(1, 10)) = 3
        // _RimThreshold("边缘光阈值", Range(0, 1)) = 0.2

        // --- SDF 面部阴影 ---
        [Toggle(_USE_SDF_SHADOW)] _UseSdfShadow("使用SDF阴影", Float) = 0
        _SDFTex("SDF阴影贴图", 2D) = "white" {}
        _SDFShadowColor("SDF阴影颜色", Color) = (0.7,0.4,0.4,1)
        _SDFBlend("SDF混合强度", Range(0, 1)) = 1 // 保留混合选项，但主要逻辑会改变
        _SDFDirectionOffset("SDF面部朝向偏移", Range(-1, 1)) = 0.5 // 重命名并调整用途
        _SDFThreshold("SDF基础阈值", Range(-1, 1)) = 0
        _SDFDetailStrength("SDF细节强度", Range(0,1)) = 0.3
        _SDFBaseStrength("SDF基础强度", Range(0,1)) = 0.7
        _SDFSmoothness("SDF平滑度", Range(0, 1)) = 0.1
        [HideInInspector] _FaceDirectionWS ("Face Direction WS", Vector) = (0,0,1,0) // 新增：接收面部朝向（世界空间）

        // --- 印堂阴影 ---
        [Toggle(_USE_FOREHEAD_SHADOW)] _UseForheadShadow("启用印堂阴影", Float) = 0
        _ForheadShadowColor("印堂阴影颜色", Color) = (0,0,0,0.5)
        _ForheadShadowPosition("印堂阴影位置", Range(0.4, 1)) = 0.6
        _ForheadShadowSize("印堂阴影大小", Range(0.01, 0.2)) = 0.08
        _ForheadShadowBlend("印堂阴影混合", Range(0, 1)) = 0.7

        // --- ID 图过滤 ---
        [Toggle(_USE_ID_MAP)] _UseIDMap("使用ID图过滤皮肤", Float) = 0
        _IDMap("ID遮罩图", 2D) = "white" {}
        _SkinID("皮肤ID值 (R通道)", Range(0, 1)) = 1.0
        _IDTolerance("ID容差", Range(0, 0.1)) = 0.01
        _NonSkinColor("非皮肤颜色处理", Color) = (1,1,1,1) 
        [Toggle(_KEEP_ORIGINAL_NON_SKIN)] _KeepOriginalNonSkin("保留非皮肤原始颜色", Float) = 1

        // --- 非皮肤 PBR (简化Blinn-Phong) ---
        [Toggle(_USE_PBR_NON_SKIN)] _UsePBRNonSkin("非皮肤使用PBR", Float) = 0
        [Toggle(_NORMALMAP)] _EnableNormalMap ("启用 法线贴图", Float) = 1.0
        [NoScaleOffset] _NormalMap("法线贴图(RG=法线,B=高光遮罩)", 2D) = "bump" {}
        _NormalScale("法线强度", Range(0, 2)) = 1.0
        _SpecHighlightMultiplier("法线B通道高光倍数", Range(0, 5)) = 1.0
        _SpecColor("高光颜色 (PBR)", Color) = (1, 1, 1, 1)
        _SpecularScale("高光强度 (PBR)", Range(0, 1)) = 0.5
        _Smoothness("平滑度 (PBR)", Range(0, 1)) = 0.5
        _PBRShadowThreshold("PBR阴影阈值", Range(0, 1)) = 0.5 
        _PBRShadowSmoothness("PBR阴影平滑度", Range(0, 0.2)) = 0.05

        // --- 描边 ---
        [Toggle(_OUTLINE)] _Outline("描边", Float) = 1
        _OutlineColor("描边颜色", Color) = (0,0,0,1)
        _OutlineWidth("描边宽度", Range(0, 0.1)) = 0.01
        [Toggle(_USE_VERTEX_COLOR_FOR_OUTLINE)] _UseVertexColorForOutline("使用顶点色控制描边粗细 (R通道)", Float) = 0
        [Toggle(_USE_MASK_FOR_OUTLINE)] _UseMaskForOutline("使用遮罩图控制描边", Float) = 0
        _OutlineMask("描边遮罩图 (R通道)", 2D) = "white" {}
        _OutlineMaskPower("遮罩强度", Range(0, 2)) = 1.0

        // 在Properties部分添加
        [Header(Eyebrow Mask)]
        [Toggle(_OUTPUT_EYEBROW_MASK)] _OutputEyebrowMask("输出眉毛遮罩", Float) = 0
        _EyebrowMaskStrength("眉毛遮罩强度", Range(0, 1)) = 1.0
        _EyebrowThreshold("眉毛阈值", Range(0, 0.3)) = 0.1 // 新增阈值控制参数

        // --- 工作流程控制 ---
        [HideInInspector] _Surface("__surface", Float) = 0.0
        [HideInInspector] _Blend("__blend", Float) = 0.0
        [HideInInspector] _AlphaClip("__clip", Float) = 0.0
        [HideInInspector] _SrcBlend("__src", Float) = 1.0
        [HideInInspector] _DstBlend("__dst", Float) = 0.0
        [HideInInspector] _ZWrite("__zw", Float) = 1.0
        [HideInInspector] _Cull("__cull", Float) = 2.0
        [HideInInspector] _ReceiveShadows("Receive Shadows", Float) = 1.0

        // --- Surface Options ---
        [Header(Surface Options)]
        [Enum(UnityEngine.Rendering.CullMode)] _Cull("Cull Mode", Float) = 2 // Back
        [Enum(UnityEngine.Rendering.BlendMode)] _SrcBlend("Src Blend", Float) = 1 // One
        [Enum(UnityEngine.Rendering.BlendMode)] _DstBlend("Dst Blend", Float) = 0 // Zero
        [Enum(UnityEngine.Rendering.BlendOp)] _BlendOp("Blend Operation", Float) = 0 // Add
        [Toggle] _ZWrite("ZWrite", Float) = 1
        [Enum(UnityEngine.Rendering.CompareFunction)] _ZTest("ZTest", Float) = 4 // LEqual

        // --- Stencil Settings ---
        [Header(Stencil Settings)]
        _StencilRef("Stencil Ref", Float) = 0
        [Enum(UnityEngine.Rendering.CompareFunction)] _StencilComp("Stencil Comp", Float) = 8 // Always
        [Enum(UnityEngine.Rendering.StencilOp)] _StencilPass("Stencil Pass", Float) = 0 // Keep
        [Enum(UnityEngine.Rendering.StencilOp)] _StencilFail("Stencil Fail", Float) = 0 // Keep
        [Enum(UnityEngine.Rendering.StencilOp)] _StencilZFail("Stencil ZFail", Float) = 0 // Keep
        [IntRange] _StencilReadMask("Read Mask", Range(0, 255)) = 255
        [IntRange] _StencilWriteMask("Write Mask", Range(0, 255)) = 255

        // --- Overlay Settings ---
        [Header(Overlay Settings)]
        [Toggle] _DrawOverlay("Enable Overlay", Float) = 0
        [Enum(UnityEngine.Rendering.BlendMode)] _OverlaySrcBlend("Overlay Src Blend", Float) = 1 // One
        [Enum(UnityEngine.Rendering.BlendMode)] _OverlayDstBlend("Overlay Dst Blend", Float) = 0 // Zero
        [Enum(UnityEngine.Rendering.BlendOp)] _OverlayBlendOp("Overlay Blend Op", Float) = 0 // Add
        _OverlayStencilRef("Overlay Stencil Ref", Float) = 0
        [Enum(UnityEngine.Rendering.CompareFunction)] _OverlayStencilComp("Overlay Stencil Comp", Float) = 8 // Always

    }

    SubShader
    {
        Tags { "RenderType" = "Opaque" "RenderPipeline" = "UniversalPipeline" "Queue" = "Geometry" }
        LOD 300
        

        // --- 描边 Pass ---
        Pass
        {
            Name "Outline"
            Tags { "LightMode" = "SRPDefaultUnlit" }
            Cull Front
            ZWrite On
            
            HLSLPROGRAM
            #pragma vertex vert
            #pragma fragment frag
            #pragma shader_feature_local _OUTLINE
            #pragma shader_feature_local _USE_VERTEX_COLOR_FOR_OUTLINE
            #pragma shader_feature_local _USE_MASK_FOR_OUTLINE
            
            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl"
            
            TEXTURE2D(_OutlineMask); SAMPLER(sampler_OutlineMask);
            
            struct Attributes
            {
                float4 positionOS : POSITION;
                float3 normalOS : NORMAL;
                float2 texcoord : TEXCOORD0;
                float4 color : COLOR;
                UNITY_VERTEX_INPUT_INSTANCE_ID
            };

            struct Varyings
            {
                float4 positionCS : SV_POSITION;
                UNITY_VERTEX_INPUT_INSTANCE_ID
            };

            CBUFFER_START(UnityPerMaterial)
            float _OutlineWidth;
            float4 _OutlineColor;
            float _OutlineMaskPower;
            float4 _BaseMap_ST;
            float _EyebrowThreshold;
            CBUFFER_END

            Varyings vert(Attributes input)
            {
                Varyings output = (Varyings)0;
                UNITY_SETUP_INSTANCE_ID(input);
                UNITY_TRANSFER_INSTANCE_ID(input, output);
                
                #if defined(_OUTLINE)
                    float3 normalOS = normalize(input.normalOS);
                    float outlineWidth = _OutlineWidth;
                    
                    #if defined(_USE_MASK_FOR_OUTLINE)
                        float2 uv = TRANSFORM_TEX(input.texcoord, _BaseMap);
                        float mask = SAMPLE_TEXTURE2D_LOD(_OutlineMask, sampler_OutlineMask, uv, 0).r;
                        outlineWidth *= mask * _OutlineMaskPower;
                    #elif defined(_USE_VERTEX_COLOR_FOR_OUTLINE)
                        outlineWidth *= input.color.r;
                    #endif
                    
                    float3 positionOS = input.positionOS.xyz + normalOS * outlineWidth;
                    output.positionCS = TransformObjectToHClip(positionOS);
                #else
                    output.positionCS = TransformObjectToHClip(input.positionOS.xyz);
                #endif
                
                return output;
            }

            half4 frag(Varyings input) : SV_Target
            {
                UNITY_SETUP_INSTANCE_ID(input);
                return _OutlineColor;
            }
            ENDHLSL
        }

        // --- 眉毛遮罩输出 Pass ---
        Pass
        {
            Name "EyebrowMaskOutput"
            Tags { "LightMode" = "SRPDefaultUnlit" }

            ZWrite Off
            Blend Off
            Cull [_Cull]

            HLSLPROGRAM
            #pragma vertex vert
            #pragma fragment fragMaskOutput

            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl"
            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/SurfaceInput.hlsl" // 包含 SurfaceInput 以使用 GetVertexPositionInputs 等

            struct Attributes
            {
                float4 positionOS : POSITION;
                float3 normalOS   : NORMAL; // 添加法线输入
                float2 texcoord   : TEXCOORD0;
                UNITY_VERTEX_INPUT_INSTANCE_ID
            };

            struct VaryingsMask
            {
                float4 positionCS : SV_POSITION;
                float2 uv         : TEXCOORD0;
                float3 normalWS   : TEXCOORD1; // 添加世界空间法线
                float3 viewDirWS  : TEXCOORD2; // 添加世界空间视图方向
                UNITY_VERTEX_INPUT_INSTANCE_ID
                UNITY_VERTEX_OUTPUT_STEREO
            };

            CBUFFER_START(UnityPerMaterial)
                float4 _BaseMap_ST;
                float _EyebrowMaskStrength;
                float _EyebrowThreshold;
                // 移除不再需要的 _SkinID 和 _IDTolerance
                // float _SkinID;
                // float _IDTolerance;
            CBUFFER_END

            TEXTURE2D(_IDMap); SAMPLER(sampler_IDMap);

            // 定义视角阈值 (cos(75 degrees) approx 0.2588)
            // 如果 dot(viewDir, normal) 小于这个值，则不输出遮罩
            static const float VIEW_ANGLE_THRESHOLD = 0.2588;

            VaryingsMask vert(Attributes input)
            {
                VaryingsMask output = (VaryingsMask)0;
                UNITY_SETUP_INSTANCE_ID(input);
                UNITY_TRANSFER_INSTANCE_ID(input, output);
                UNITY_INITIALIZE_VERTEX_OUTPUT_STEREO(output);

                VertexPositionInputs vertexInput = GetVertexPositionInputs(input.positionOS.xyz);
                VertexNormalInputs normalInput = GetVertexNormalInputs(input.normalOS); // 获取法线输入

                output.positionCS = vertexInput.positionCS;
                output.uv = TRANSFORM_TEX(input.texcoord, _BaseMap);
                output.normalWS = normalInput.normalWS; // 传递世界空间法线
                output.viewDirWS = GetWorldSpaceNormalizeViewDir(vertexInput.positionWS); // 传递世界空间视图方向

                return output;
            }

            half4 fragMaskOutput(VaryingsMask input) : SV_Target
            {
                UNITY_SETUP_INSTANCE_ID(input);
                UNITY_SETUP_STEREO_EYE_INDEX_POST_VERTEX(input);

                // --- 视角检查 ---
                float3 normalWS = normalize(input.normalWS);
                float3 viewDirWS = normalize(input.viewDirWS);
                half NdotV = dot(normalWS, viewDirWS);

                // 如果视角点积小于阈值 (角度大于75度或从背面看)，则直接输出黑色
                if (NdotV < VIEW_ANGLE_THRESHOLD)
                {
                    return half4(0, 0, 0, 1.0);
                }

                // --- UV 区域检查 ---
                // 判断是否在下半部分(UV坐标系中Y<0.7为下半部分) - 根据你的模型UV布局调整此值
                if (input.uv.y < 0.7)
                {
                    // 下半部分直接输出黑色
                    return half4(0, 0, 0, 1.0);
                }

                // --- 正常的眉毛遮罩计算 (仅在上半部分且视角合适时执行) ---
                // 从ID图获取R通道值并倒置
                half idValue = 1.0 - SAMPLE_TEXTURE2D(_IDMap, sampler_IDMap, input.uv).r;

                // 判断是否为眉毛区域 - 倒置后白色区域为眉毛
                bool isEyebrow = idValue > _EyebrowThreshold;

                // 眉毛区域输出白色，非眉毛区域输出黑色
                half eyebrowMask = isEyebrow ? 1.0 : 0.0;

                // 应用强度系数
                eyebrowMask *= _EyebrowMaskStrength;

                return half4(eyebrowMask, eyebrowMask, eyebrowMask, 1.0);
            }
            ENDHLSL
        }

        // --- 主 Pass - URP前向渲染 ---
        Pass
        {
            Name "ForwardLit"
            Tags { "LightMode" = "UniversalForward" }
            Blend [_SrcBlend][_DstBlend]
            ZWrite [_ZWrite]
            Cull [_Cull]
            ZTest [_ZTest]

            Stencil
            {
                Ref [_StencilRef]
                Comp [_StencilComp]
                Pass [_StencilPass]
                Fail [_StencilFail]
                ZFail [_StencilZFail]
                ReadMask [_StencilReadMask]
                WriteMask [_StencilWriteMask]
            }

            HLSLPROGRAM
            #pragma vertex vert
            #pragma fragment frag
            #pragma prefer_hlslcc gles
            #pragma exclude_renderers d3d11_9x
            
            #pragma multi_compile _ _MAIN_LIGHT_SHADOWS
            #pragma multi_compile _ _MAIN_LIGHT_SHADOWS_CASCADE
            #pragma multi_compile _ _ADDITIONAL_LIGHTS_VERTEX _ADDITIONAL_LIGHTS
            #pragma multi_compile _ _SHADOWS_SOFT
            #pragma multi_compile_fog
            
            #pragma shader_feature_local _RIM_LIGHTING
            #pragma shader_feature_local _SPECULAR
            #pragma shader_feature_local _USE_SDF_SHADOW
            #pragma shader_feature_local _USE_ID_MAP
            #pragma shader_feature_local _KEEP_ORIGINAL_NON_SKIN
            #pragma shader_feature_local _USE_PBR_NON_SKIN
            #pragma shader_feature_local _NORMALMAP
            #pragma shader_feature_local _USE_FOREHEAD_SHADOW

            
            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Core.hlsl"
            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Lighting.hlsl"
            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/SurfaceInput.hlsl"
            
            struct Attributes
            {
                float4 positionOS : POSITION;
                float3 normalOS : NORMAL;
                float2 texcoord : TEXCOORD0;
                float4 color : COLOR;
                #if defined(_NORMALMAP)
                float4 tangentOS : TANGENT;
                #endif
                UNITY_VERTEX_INPUT_INSTANCE_ID
            };

            struct Varyings
            {
                float4 positionCS : SV_POSITION;
                float2 uv : TEXCOORD0;
                float3 positionWS : TEXCOORD1;
                float3 normalWS : TEXCOORD2;
                float4 color : COLOR;
                #if defined(_NORMALMAP)
                float4 tangentWS : TEXCOORD3;
                #endif
                float3 viewDirWS : TEXCOORD4;
                float fogFactor : TEXCOORD5;
                #if defined(REQUIRES_VERTEX_SHADOW_COORD_INTERPOLATOR)
                float4 shadowCoord : TEXCOORD6;
                #endif
                #if defined(REQUIRES_LIGHTMAP_UV_INTERPOLATOR)
                float2 lightmapUV : TEXCOORD7;
                #endif
                /*
                #if defined(_USE_HAIR_EFFECTS)
                float3 normalVS : TEXCOORD8;
                #endif
                */
                UNITY_VERTEX_INPUT_INSTANCE_ID
                UNITY_VERTEX_OUTPUT_STEREO
            };

            CBUFFER_START(UnityPerMaterial)
            float4 _BaseMap_ST; float4 _BaseColor;
            float4 _BrightColor; float4 _MidColor; float4 _DarkColor;
            float _BrightThreshold; float _DarkThreshold; float _ShadowSmooth;
            float4 _ToonSpecularColor; float _ToonSpecularSize; float _ToonSpecularSmoothness;
            float4 _RimColor; float _RimPower; float _RimThreshold;
            float _OutlineWidth; float4 _OutlineColor;
            float _SDFBlend; float _SDFThreshold; float _SDFSmoothness; float _SDFDirectionOffset; float4 _SDFShadowColor;
            float3 _FaceDirectionWS; // 新增：声明面部朝向变量
            float _SkinID; float _IDTolerance; float4 _NonSkinColor;
            float4 _SpecColor; float _SpecularScale; float _Smoothness;
            float _NormalScale; float _SpecHighlightMultiplier;
            float _PBRShadowThreshold; float _PBRShadowSmoothness;
            float _SDFDetailStrength;
            float _SDFBaseStrength;
            float _OutputEyebrowMask;
            float _EyebrowMaskStrength;
            float _AmbientIntensity; // 新增环境光强度变量
            float4 _ForheadShadowColor;
            float _ForheadShadowPosition;
            float _ForheadShadowSize;
            float _ForheadShadowBlend;
            /*
            float _HairAOIntensity;
            float _MatCapIntensity;
            */
            CBUFFER_END

            TEXTURE2D(_SDFTex); SAMPLER(sampler_SDFTex);
            TEXTURE2D(_IDMap); SAMPLER(sampler_IDMap);
            TEXTURE2D(_NormalMap); SAMPLER(sampler_NormalMap);
            /*
            TEXTURE2D(_HairEffectMap); SAMPLER(sampler_HairEffectMap);
            TEXTURE2D(_MatCapTex); SAMPLER(sampler_MatCapTex);
            */

            Varyings vert(Attributes input)
            {
                Varyings output = (Varyings)0;
                UNITY_SETUP_INSTANCE_ID(input);
                UNITY_TRANSFER_INSTANCE_ID(input, output);
                UNITY_INITIALIZE_VERTEX_OUTPUT_STEREO(output);

                output.color = input.color;
                output.uv = TRANSFORM_TEX(input.texcoord, _BaseMap);

                VertexPositionInputs vertexInput = GetVertexPositionInputs(input.positionOS.xyz);
                VertexNormalInputs normalInput = GetVertexNormalInputs(input.normalOS);

                output.positionCS = vertexInput.positionCS;
                output.positionWS = vertexInput.positionWS;
                output.normalWS = normalInput.normalWS;
                output.viewDirWS = GetWorldSpaceNormalizeViewDir(vertexInput.positionWS);
                output.fogFactor = ComputeFogFactor(vertexInput.positionCS.z);

                #if defined(_NORMALMAP)
                    float sign = input.tangentOS.w * GetOddNegativeScale();
                    output.tangentWS = float4(normalInput.tangentWS, sign);
                #endif

                /*
                #if defined(_USE_HAIR_EFFECTS)
                    output.normalVS = TransformWorldToViewDir(normalInput.normalWS);
                #endif
                */

                #if defined(REQUIRES_VERTEX_SHADOW_COORD_INTERPOLATOR)
                    output.shadowCoord = GetShadowCoord(vertexInput);
                #endif
                #if defined(REQUIRES_LIGHTMAP_UV_INTERPOLATOR)
                    output.lightmapUV = input.lightmapUV * unity_LightmapST.xy + unity_LightmapST.zw;
                #endif

                return output;
            }

            float smoothTransition(float value, float threshold, float smooth)
            {
                return smoothstep(threshold - smooth, threshold + smooth, value);
            }

            half4 frag(Varyings input) : SV_Target
            {
                UNITY_SETUP_INSTANCE_ID(input);
                UNITY_SETUP_STEREO_EYE_INDEX_POST_VERTEX(input);
                
                half4 baseColor = SAMPLE_TEXTURE2D(_BaseMap, sampler_BaseMap, input.uv) * _BaseColor;
                
                float3 normalWS = normalize(input.normalWS);
                
                // 定义高光遮罩变量，默认值为1（无遮罩）
                half specularMaskMap = 1.0;

                // ...existing code...
                
                #if defined(_NORMALMAP)
                    half4 normalSample = SAMPLE_TEXTURE2D(_NormalMap, sampler_NormalMap, input.uv);
                    
                    // 保留B通道作为高光遮罩的提取
                    specularMaskMap = normalSample.b * _SpecHighlightMultiplier;
                    
                    // 兼容处理法线贴图 - 混合处理方式
                    half3 normalTS;
                    
                    // 检查是否是标准格式的法线贴图 (通过检查G通道，标准法线贴图G通道值通常大于0.5)
                    if (normalSample.g > 0.5)
                    {
                        // 使用标准法线解码方法
                        normalTS = UnpackNormalScale(normalSample, _NormalScale);
                    }
                    else
                    {
                        // 使用原来的高度图梯度方法，可能更适合特殊处理的区域
                        float height = dot(normalSample.rgb, float3(0.299, 0.587, 0.114));
                        float2 u_offset = float2(1.0/1024.0, 0);
                        float2 v_offset = float2(0, 1.0/1024.0);
                        float heightU = dot(SAMPLE_TEXTURE2D(_NormalMap, sampler_NormalMap, input.uv + u_offset).rgb, float3(0.299, 0.587, 0.114));
                        float heightV = dot(SAMPLE_TEXTURE2D(_NormalMap, sampler_NormalMap, input.uv + v_offset).rgb, float3(0.299, 0.587, 0.114));
                        float2 gradient = float2(heightU - height, heightV - height) * _NormalScale;
                        normalTS = normalize(float3(-gradient.x, -gradient.y, 1.0));
                    }
                    
                    // 确保TBN矩阵计算正确
                    float3 tangentWS = normalize(input.tangentWS.xyz);
                    float sgn = input.tangentWS.w;
                    float3 bitangentWS = sgn * cross(normalWS, tangentWS);
                    
                    // 确保正交性以减少扭曲
                    bitangentWS = normalize(bitangentWS - dot(bitangentWS, tangentWS) * tangentWS);
                    
                    // 构建TBN矩阵
                    float3x3 tangentToWorld = float3x3(tangentWS, bitangentWS, normalWS);
                    
                    // 将法线从切线空间转换到世界空间并确保单位长度
                    normalWS = normalize(TransformTangentToWorld(normalTS, tangentToWorld));
                    
                #endif

                float3 viewDirWS = normalize(input.viewDirWS);

                // --- 获取主光源信息 ---
                Light mainLight;
                #if defined(REQUIRES_VERTEX_SHADOW_COORD_INTERPOLATOR)
                    // 如果需要阴影坐标，则使用带 shadowCoord 的 GetMainLight
                    mainLight = GetMainLight(input.shadowCoord);
                #else
                    // 否则，使用不带 shadowCoord 的 GetMainLight
                    mainLight = GetMainLight();
                #endif

                
                float3 lightDir = mainLight.direction;
                float3 lightColor = mainLight.color * 0.7;
                half shadowAttenuation = mainLight.shadowAttenuation;

                half3 finalPixelColor = 0;
                half finalAlpha = baseColor.a;
                bool isSkin = true; 

                #if defined(_USE_ID_MAP)
                    half idValue = SAMPLE_TEXTURE2D(_IDMap, sampler_IDMap, input.uv).r;
                    
                    isSkin = abs(idValue - _SkinID) < _IDTolerance;
                    
                    if (!isSkin) // 如果不是皮肤
                    {
                        #if defined(_USE_PBR_NON_SKIN)
                            // --- 非皮肤 PBR 计算 ---
                            half rawNdotL = dot(normalWS, lightDir);
                            half halfLambertPBR = rawNdotL * 0.5 + 0.5;

                            half pbrLightFactor = smoothstep(_PBRShadowThreshold - _PBRShadowSmoothness, 
                                                             _PBRShadowThreshold + _PBRShadowSmoothness, 
                                                             halfLambertPBR);

                            half3 diffuse = baseColor.rgb * lightColor * pbrLightFactor; 

                            half3 halfVec = normalize(lightDir + viewDirWS);
                            half NdotH = saturate(dot(normalWS, halfVec));
                            half specPower = exp2(10 * _Smoothness + 1); 
                            half specIntensity = pow(NdotH, specPower) * _SpecularScale;
                            // 应用高光遮罩到PBR高光计算
                            half3 specular = _SpecColor.rgb * lightColor * specIntensity * pbrLightFactor * specularMaskMap; 

                            half3 indirectDiffuse = SampleSH(normalWS);

                            half3 directLight = diffuse + specular;
                            finalPixelColor = directLight * shadowAttenuation + indirectDiffuse * baseColor.rgb;

                            // 应用雾效并返回 (重要: 阻止执行后续的皮肤代码)
                            finalPixelColor = MixFog(finalPixelColor, input.fogFactor);
                            return half4(finalPixelColor, baseColor.a); 

                        #else // 非皮肤，但不使用PBR
                            #if defined(_KEEP_ORIGINAL_NON_SKIN)
                                // 返回原始颜色 (重要: 阻止执行后续的皮肤代码)
                                finalPixelColor = baseColor.rgb; // Assign base color before fog
                            #else
                                // 返回处理后颜色 (重要: 阻止执行后续的皮肤代码)
                                finalPixelColor = baseColor.rgb * _NonSkinColor.rgb; // Assign processed color before fog
                            #endif
                            // Apply fog and return for non-PBR non-skin cases too
                            finalPixelColor = MixFog(finalPixelColor, input.fogFactor);
                            return half4(finalPixelColor, baseColor.a); 
                        #endif
                    }
                    // 如果是皮肤 (isSkin is true)，则跳过上面的 if (!isSkin) 块，继续执行下面的代码
                #endif
                
                // --- 皮肤区域 NPR 计算 ---
                half3 skinColor = 1; // Initialize skin color factor
                float NdotL_Toon = dot(normalWS, lightDir); // Calculate NdotL once for skin

                #if defined(_USE_SDF_SHADOW)
                    // 构建头部坐标系
                    float3 headForward = normalize(_FaceDirectionWS);
                    float3 headRight = normalize(cross(float3(0,1,0), headForward));
                    float3 headUp = cross(headRight, headForward);
                
                    // 投影光照方向
                    float3 fixedLightDirWS = -normalize(lightDir - dot(lightDir, headUp)*headUp);
                    
                    // 动态UV镜像
                    float horizontalDot = dot(fixedLightDirWS, headRight);
                    float2 sdfUV = input.uv;
                    sdfUV.x = (horizontalDot > 0) ? sdfUV.x : 1 - sdfUV.x;
                
                    // 双通道采样
                    half2 sdfData = SAMPLE_TEXTURE2D(_SDFTex, sampler_SDFTex, sdfUV).rg;
                
                    // 动态阈值计算
                    float verticalDot = dot(fixedLightDirWS, headForward);
                    float baseThreshold = verticalDot * 0.5 + 0.5;
                    float sdfThreshold = baseThreshold + _SDFThreshold * 0.5;
                
                    // 分层阴影混合
                    float baseShadow = smoothstep(sdfThreshold - _SDFSmoothness*0.5,
                                                sdfThreshold + _SDFSmoothness*0.5,
                                                sdfData.r);
                    float detailShadow = smoothstep(sdfThreshold - _SDFSmoothness*1.2,
                                                sdfThreshold + _SDFSmoothness*1.2,
                                                sdfData.g);
                    float shadowFactor = saturate(baseShadow * _SDFBaseStrength + detailShadow * _SDFDetailStrength);
                    
                    // 应用印堂阴影
                    #if defined(_USE_FOREHEAD_SHADOW)
                        // 确定印堂区域 - 根据UV坐标判断是否在额头区域
                        // 通常面部UV布局中，额头区域在Y轴较高位置
                        float forheadMask = 0;
                        if (input.uv.y > _ForheadShadowPosition - _ForheadShadowSize && 
                            input.uv.y < _ForheadShadowPosition + _ForheadShadowSize) 
                        {
                            // 创建渐变过渡的遮罩
                            float distFromCenter = abs(input.uv.y - _ForheadShadowPosition) / _ForheadShadowSize;
                            forheadMask = 1.0 - smoothstep(0.5, 1.0, distFromCenter);
                            forheadMask *= _ForheadShadowBlend;
                        }
                        
                        // 应用印堂阴影
                        half4 blendedShadowColor = lerp(half4(1,1,1,1), _ForheadShadowColor, forheadMask);
                        skinColor = lerp(_SDFShadowColor.rgb, _BrightColor.rgb, shadowFactor) * blendedShadowColor.rgb;
                    #else
                        // 原始SDF阴影计算
                        skinColor = lerp(_SDFShadowColor.rgb, _BrightColor.rgb, shadowFactor);
                    #endif
                #else
                    // --- 使用三色阶着色 ---
                    float halfLambert = NdotL_Toon * 0.5 + 0.5;
                    float brightArea = smoothTransition(halfLambert, _BrightThreshold, _ShadowSmooth);
                    float darkArea = 1.0 - smoothTransition(halfLambert, _DarkThreshold, _ShadowSmooth);
                    float midArea = saturate(1.0 - brightArea - darkArea);
                    half3 baseNPRColor = 
                        _BrightColor.rgb * brightArea + 
                        _MidColor.rgb * midArea + 
                        _DarkColor.rgb * darkArea;

                    // 应用印堂阴影到三色阶模式
                    #if defined(_USE_FOREHEAD_SHADOW)
                        float forheadMask = 0;
                        if (input.uv.y > _ForheadShadowPosition - _ForheadShadowSize && 
                            input.uv.y < _ForheadShadowPosition + _ForheadShadowSize) 
                        {
                            float distFromCenter = abs(input.uv.y - _ForheadShadowPosition) / _ForheadShadowSize;
                            forheadMask = 1.0 - smoothstep(0.5, 1.0, distFromCenter);
                            forheadMask *= _ForheadShadowBlend;
                        }
                        
                        half4 blendedShadowColor = lerp(half4(1,1,1,1), _ForheadShadowColor, forheadMask);
                        skinColor = baseNPRColor * blendedShadowColor.rgb;
                    #else
                        skinColor = baseNPRColor;
                    #endif
                #endif
                
                // --- 计算皮肤高光 ---
                half3 toonSpecular = 0;
                #if defined(_SPECULAR)
                    half3 halfVecToon = normalize(viewDirWS + lightDir);
                    half NdotHToon = saturate(dot(normalWS, halfVecToon)); 
                    half specMaskBase = pow(NdotHToon, exp2( (1.0 - _ToonSpecularSize) * 10.0 + 1.0)); 
                    half specularMask = smoothstep(0.5 - _ToonSpecularSmoothness, 
                                                  0.5 + _ToonSpecularSmoothness, 
                                                  specMaskBase); 
                    
                    float lightAreaMask = 1.0;
                    #if defined(_USE_SDF_SHADOW)
                        // SDF模式下，高光只应出现在SDF计算出的亮部 (sdfFactor > 0.5 左右)
                        // Re-use sdfFactor calculated earlier if _USE_SDF_SHADOW is defined
                        lightAreaMask = smoothstep(0.5 - _SDFSmoothness, 0.5 + _SDFSmoothness, sdfFactor); 
                    #else
                        // 三色阶模式下，高光只应出现在亮部
                        // Re-use halfLambert calculated earlier if _USE_SDF_SHADOW is not defined
                        float halfLambert = NdotL_Toon * 0.5 + 0.5; // Ensure halfLambert is available
                        lightAreaMask = smoothTransition(halfLambert, _BrightThreshold, _ShadowSmooth);
                    #endif

                    toonSpecular = _ToonSpecularColor.rgb * specularMask * lightAreaMask * specularMaskMap;
                #endif
                
                // --- 计算边缘光 ---
                half3 rimLight = 0;
                #if defined(_RIM_LIGHTING)




                #endif
                
                // --- 添加环境光影响 ---
                half3 ambientLight = SampleSH(normalWS) * _AmbientIntensity;
                
                // --- 组合最终颜色 ---
                half3 finalNPRColor = baseColor.rgb * skinColor * lightColor * shadowAttenuation + 
                                     baseColor.rgb * skinColor * ambientLight + 
                                     toonSpecular + rimLight;
                finalPixelColor = finalNPRColor;

                
                // 原始return语句保持不变
                finalPixelColor = MixFog(finalPixelColor, input.fogFactor);
                return half4(finalPixelColor, finalAlpha);
            }
            ENDHLSL
        }




    }
    
    FallBack "Universal Render Pipeline/Lit"
    CustomEditor "UnityEditor.ShaderGraph.PBRMasterGUI"
}

